package com.qidian.server.workerThread;

import java.sql.Connection;
import java.sql.PreparedStatement;
import java.sql.Statement;
import java.util.Iterator;
import java.util.concurrent.ConcurrentHashMap;

import org.apache.log4j.Logger;

import com.qidian.common.Constants;
import com.qidian.common.Globals;
import com.qidian.common.beanCache.MessageStatusCounter;
import com.qidian.common.beans.AccountBean;
import com.qidian.common.beans.MessageBean;
import com.qidian.common.beans.UserBean;
import com.qidian.connection.util.ConnectionPool;
import com.qidian.server.MServer;



/**
 *  将缓存中已回答的消息保存到数据库中。
 * 
 * */
public class Synchronizer_Message extends WorkerThread
{
	private static Logger logger = Logger.getLogger(Synchronizer_Message.class) ;
	private static Synchronizer_Message messageSynchronizer = new Synchronizer_Message() ;
	
//	private long interval = 30*1000 ;
	
	private Synchronizer_Message()
	{
		
	}
	
	
	public static Synchronizer_Message getInstance()
	{
		return messageSynchronizer ;
	}
	
    public void init()
    {
        // TODO Auto-generated method stub
        
    }
    
    public void run()
    {
    	
    	int loopTimes = 0 ;
    	try
    	{
    		MessageBean msg = new MessageBean() ;
            ConcurrentHashMap<Long,MessageBean> msgBuf = Globals.getMessageBuffer().buffer ;
            MessageStatusCounter msCounter = Globals.getMessageBuffer().mscounter ;
	    	while(keepRunning)
	    	{
            	loopTimes ++ ;
	        	Connection conn = null ;
	        	PreparedStatement ps = null ;
	    		try
		    	{
			    	conn = ConnectionPool.getConnection() ;
			    	ps = msg.getPreparedStatement(conn) ;
	    			Iterator<MessageBean> msgItr = msgBuf.values().iterator() ;
	    			msCounter.reset() ;
	    	    	int batchSize = 0 ;
	    			while(msgItr.hasNext())
	    			{
	    				msg = msgItr.next() ;
	    				
	    				if (msg.isTimeOut())
	    					msg.setTimeOut() ;
	    				
	    				// 是否到了同步时间,将消息从缓存转存至数据库
	    				if (msg.isTimeToSync())
	    				{
	    					// 从缓冲区移除
	    					msgBuf.remove(((MessageBean)msg).getId()) ;
	    					
	    					// 如果非正确答案，则返回题分
	    					if (!msg.isCorrentMsg())
	    						MServer.getInstance().s_returnAccountPoint(msg) ;

	    					// 是否需要同步到数据库
	    					if (msg.needSynchronized())
	    					{	
		    					if(!msg.setParameters(ps))
		    						continue;	
		    					ps.addBatch() ;
		    					batchSize ++ ;
		    				}
	    					
	    					// 释放文件内容所占内存
	    					msg.setContent(null) ;

	    				}
	    				
	    				if (batchSize%500 == 499)
	    				{
	    					ps.executeBatch() ;
	    					ps.clearBatch() ;
	    					ps.clearParameters() ;
	    				}
	    				
	    				msCounter.add(msg.getStatus());
	    			}
	    			
	    			ps.executeBatch() ;
	    			ps.clearBatch() ;
	    			ps.close() ;
	    			
                    // clear up much slower
                    if(loopTimes%300 == 0)
                    {
//                    	System.out.println("Current msg buffer size："+msgBuf.size());
                    	Statement stt = conn.createStatement() ;
                    	stt.executeUpdate(MessageBean.clearSQLPrefix+(System.currentTimeMillis()-Constants.message_keep_time)) ;
                    	stt.close() ;
                    }
			    	logger.debug("Batch size:"+batchSize) ;
	    			
		    	}
		    	catch (Exception e)
		    	{
		    		Globals.getMessageBuffer().print() ;
		    		e.printStackTrace() ;
		    		logger.error(e.getMessage()) ;
		    	}
		    	finally
		    	{
		    		ConnectionPool.freeConn(conn) ;
		    	}
		    	
		    	Thread.sleep(interval) ;
//		    	System.out.println(msCounter) ;

	    	}
    	}
    	catch(Exception e)
    	{
    		e.printStackTrace() ;
    		logger.error(e.getMessage()) ;
    		System.exit(-1) ;
    	}
    	
    	return ;
    }
}
